package com.ht.graphmodel;

import com.mxgraph.io.mxCodec;
import com.mxgraph.model.mxCell;
import com.mxgraph.model.mxGraphModel;
import com.mxgraph.model.mxICell;
import com.mxgraph.model.mxGeometry;
import com.mxgraph.util.mxUtils;
import com.mxgraph.layout.mxCompactTreeLayout;
import com.mxgraph.view.mxGraph;
import com.mxgraph.swing.mxGraphComponent;
import com.ht.aems.ieeeformat.IEEEDataIsland;
import com.ht.aems.ieeeformat.BusData;
import com.ht.aems.ieeeformat.BranchData;
import com.ht.aems.ieeeformat.IslandUtil;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.apache.log4j.BasicConfigurator;
import org.apache.log4j.Logger;

import javax.swing.*;
import java.util.HashMap;
import java.util.Map;
import java.util.List;
import java.io.IOException;

/**
 * Created by IntelliJ IDEA.
 *
 * @author Wang Jiaxiang
 *         Date: 2010-11-25
 */
public class IeeeNodeModel {
    //Logger log = new Logger();
    public static Map<String, double[]> getNodeAddr(String file) {
        Document document = null;
        try {
            document = mxUtils.parseXml(mxUtils.readFile(file));
        } catch (IOException e) {
            e.printStackTrace();  
        }
        mxGraphModel model = new mxGraphModel();
        mxCodec codec = new mxCodec(document);
        codec.decode(document.getDocumentElement(), model);
        Map<String, Object> cells = model.getCells();
        Map<String, double[]> result = new HashMap<String, double[]>();
        mxCell cell;
        Element ele;
        for (String key : cells.keySet()) {
            cell = (mxCell) cells.get(key);
            if (cell.isVertex()) {
                ele = (Element) cell.getValue();
                if(cell.getGeometry() == null)
                    continue;
                double x = cell.getGeometry().getX();
                double y = cell.getGeometry().getY();
                double[] xy = new double[2];
                xy[0] = x;
                xy[1] = y;
                result.put(cell.getId(), xy);
            }
        }
        return result;
    }

    public static void main(String[] args) {
        BasicConfigurator.configure();
        IeeeNodeModel model = new IeeeNodeModel();
        String fileNum="300";
        mxGraphModel mm = model.createGraphModel(IEEE2JTree.getIand("D:\\cells\\case"+ fileNum + ".txt"));
        mxGraph graph = new mxGraph();
        graph.setModel(mm);
        mxGraphComponent comp = new mxGraphComponent(graph);
        mxCompactTreeLayout layout = new mxCompactTreeLayout(graph, false);
        layout.execute(graph.getDefaultParent());
        model.writeFile(mm,"d:\\cells", "case" + fileNum + ".mxe");
        JFrame jf = new JFrame();
        jf.getContentPane().add(comp);
        jf.pack();
        jf.setVisible(true);
    }

    public mxGraphModel createGraphModel(IEEEDataIsland island) {
        List<BusData> busData = island.getBuses();
        List<BranchData> branches = island.getBranches();
        mxGraphModel model = new mxGraphModel();
        mxCell root = (mxCell) model.createRoot();
        model.setRoot(root);
        mxICell defaultParent = root.getChildAt(0);
        Document doc = mxUtils.createDocument();
        model.beginUpdate();
        int index = 0;
        mxCell cell;
        Map<Integer, mxCell>terminals = new HashMap<Integer, mxCell>(busData.size());
        for (BusData data : busData) {
            cell = new mxCell();
            cell.setVertex(true);
            cell.setConnectable(true);
            Element ele = doc.createElement("BusData");
            ele.setAttribute("BusNumber", String.valueOf(data.getBusNumber()));
            ele.setTextContent(String.valueOf(data.getBusNumber()));
            cell.setValue(ele);
            cell.setStyle("ellipse;shape=ellipse");
            mxGeometry geo = new mxGeometry();
            cell.setGeometry(geo);
            cell.getGeometry().setWidth(30);
            cell.getGeometry().setHeight(30);
            terminals.put(data.getBusNumber(), cell);
            model.add(defaultParent, cell, index++);
        }
        for (BranchData branch : branches) {
            cell = new mxCell();
            cell.setEdge(true);
            cell.setGeometry(new mxGeometry());
            cell.getGeometry().setRelative(true);
            Element ele = doc.createElement("BranchData");
            ele.setAttribute("BranchId", String.valueOf(branch.getId()));
            cell.setValue(ele);

            int sourceNum = branch.getTapBusNumber();
            mxCell source = terminals.get(sourceNum);
            int targetNum = branch.getZBusNumber();
           
            mxCell target = terminals.get(targetNum);
            model.setTerminal(cell, source, true);
            model.setTerminal(cell, target, false);
            model.add(defaultParent, cell, index++);
            cell.setStyle("endArrow=none;startArrow=none");
        }
        model.endUpdate();
        return model;
    }

    public void writeFile(mxGraphModel model, String filePath, String fileName) {
        mxCodec codec = new mxCodec();
        String xml = mxUtils.getXml(codec.encode(model));
        try {
            mxUtils.writeFile(xml, filePath +"\\"+ fileName);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}
